package com.kyrie.lib_sys.utils.learn.TimeDemo;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * 工单时间校验工具类：支持顺序校验、重叠校验，按员工分组
 */
public class TimeOverlapValidator {

    private static final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");

    /**
     * 校验时间列表是否存在顺序错误或重叠错误（按员工区分）
     * @param timeList 每个 Map 代表一条记录，必须包含 pk_psndoc(employeeId) 字段（员工），可包含 1~4 个时间字段
     * @return true 表示校验通过，false 表示有顺序或重叠错误
     */
    public static boolean validate(List<Map<String, String>> timeList) {
        // 按员工分组的时间区间集合
        Map<String, List<TimeInterval>> employeeTimeMap = new HashMap<>();

        for (int i = 0; i < timeList.size(); i++) {
            Map<String, String> task = timeList.get(i);
            String pk_psndoc = task.getOrDefault("employeeId", "unknown");

            List<LocalDateTime> timePoints = new ArrayList<>();

            if (task.containsKey("prepareTime")) timePoints.add(parse(task.get("prepareTime")));
            if (task.containsKey("travelTime")) timePoints.add(parse(task.get("travelTime")));
            if (task.containsKey("startTime")) timePoints.add(parse(task.get("startTime")));
            if (task.containsKey("completeTime")) timePoints.add(parse(task.get("completeTime")));

            // 顺序校验
            for (int j = 1; j < timePoints.size(); j++) {
                if (!timePoints.get(j - 1).isBefore(timePoints.get(j))) {
                    System.out.printf("员工 [%s] 的时间点 \"%s\" 存在时间顺序错误\n",
                            pk_psndoc, format(timePoints.get(j)));
                    return false;
                }
            }

            // 构建时间区间
            if (!timePoints.isEmpty()) {

                //对每条记录，取所有时间点的最小值和最大值，构成一个时间区间：
                LocalDateTime start = Collections.min(timePoints);
                LocalDateTime end = Collections.max(timePoints);
                TimeInterval interval = new TimeInterval(start, end, i + 1);

                List<TimeInterval> existingList = employeeTimeMap.getOrDefault(pk_psndoc, new ArrayList<>());
                for (TimeInterval exist : existingList) {
                    if (interval.overlaps(exist)) {
                        System.out.printf("员工 [%s] 的记录%d[%s ~ %s] 与记录%d[%s ~ %s] 存在时间重叠错误\n",
                                pk_psndoc,
                                interval.index, format(interval.start), format(interval.end),
                                exist.index, format(exist.start), format(exist.end));
                        return false;
                    }
                }

                existingList.add(interval);
                employeeTimeMap.put(pk_psndoc, existingList);
            }
        }

        return true;
    }

    private static LocalDateTime parse(String timeStr) {
        return LocalDateTime.parse(timeStr, formatter);
    }

    private static String format(LocalDateTime time) {
        return formatter.format(time);
    }

    /**
     * 表示时间区间
     */
    private static class TimeInterval {
        LocalDateTime start;
        LocalDateTime end;
        int index;

        TimeInterval(LocalDateTime start, LocalDateTime end, int index) {
            this.start = start;
            this.end = end;
            this.index = index;
        }

        boolean overlaps(TimeInterval other) {
            return !(this.end.isBefore(other.start) || this.start.isAfter(other.end));
        }
    }

}
